package com.ys.service.storage.impl;

import java.math.BigDecimal;
import java.util.Date;
import java.util.Map;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.ys.entity.business.TpProductBasisComponent;
import com.ys.entity.storage.TccLocation;
import com.ys.entity.storage.TccStockControl;
import com.ys.entity.storage.TccStockControlRunning;
import com.ys.entity.storage.TccStockFrozenRunning;
import com.ys.entity.storage.TccStockOpe;
import com.ys.entity.storage.TccStockSource;
import com.ys.enume.storage.TccStockSourceEnum;
import com.ys.mapper.business.DiySqlMapper;
import com.ys.mapper.hr.HrMapper;
import com.ys.mapper.storage.StorageMapper;
import com.ys.mapper.storage.TccStockControlMapper;
import com.ys.mapper.storage.TccStockControlRunningMapper;
import com.ys.mapper.storage.TccStockFrozenRunningMapper;
import com.ys.mapper.storage.TccStockOpeMapper;
import com.ys.mapper.storage.TccStockSourceMapper;
import com.ys.service.storage.TccStockControlService;
import com.ys.util.BidUtil;
import com.ys.util.DateUtil;
import com.ys.util.RandomUtil;
import com.ys.vo.R;

@Service("tccStockControlService")
public class TccStockControlServiceImpl implements TccStockControlService {
	
	private String BID_PRE = "KCXG";

	@Autowired
	private HrMapper hrMapper;
	@Autowired
	private DiySqlMapper diySqlMapper;
	@Autowired
	private StorageMapper storageMapper;
	@Autowired
	private TccStockControlMapper tccStockControlMapper;
	@Autowired
	private TccStockOpeMapper tccStockOpeMapper;
	@Autowired
	private TccStockControlRunningMapper tccStockControlRunningMapper;
	@Autowired
	private TccStockSourceMapper tccStockSourceMapper;
	@Autowired
	private TccStockFrozenRunningMapper tccStockFrozenRunningMapper;

	@Override
	public void stockOutSub(String guid, String dayAgo) {
		TccStockControl tccStockControl = new TccStockControl().setGuid(guid).queryFirst();
		if (tccStockControl == null) {
			return;
		} else if (tccStockControl.getIsParent() != TccStockSourceEnum.IsParent.NO.value) {
			return;
		} else if (new TpProductBasisComponent().setCode(tccStockControl.getProductCode()).count() == 0) {
			return;
		}

		Integer productNum = tccStockControl.getProductNum();
		Integer productNumAll = tccStockControl.getProductNumAll();
		if(productNum <= 0 || productNumAll <= 0) {
			return;
		}
		if (DateUtil.getYYYY_MM_DD(tccStockControl.getDrksj()).compareTo(dayAgo) <= 0) {
			
			// 修改库存数量
			tccStockControl
				.setProductNum(0)
				.setProductNumAll(productNumAll - productNum);
			tccStockControlMapper.update(tccStockControl);
			
			// 添加库存修改单
			TccStockOpe tccStockOpe = null;
			{
				String guid2 = RandomUtil.getGUID();
				String bid = getBidForAdd();
				String vGsMc = tccStockControl.getVgsmc();
				String vGsJc = tccStockControl.getVgsjc();
				String vGsBm = tccStockControl.getVgsbm();
				String productName = tccStockControl.getProductName();
				String productCode = tccStockControl.getProductCode();
				String locationHw = tccStockControl.getVhw();
				String locationKq = tccStockControl.getVkq();
				String locationArea = tccStockControl.getGdepot();
				String remark = "超过30天，系统自动出库";
				String createUser = "0000";
				tccStockOpe = TccStockOpe.tccStockOpe(guid2, bid, vGsMc, vGsJc, vGsBm, productName, productCode, productNum, locationHw, locationKq, locationArea, remark, createUser, 1);
				tccStockOpeMapper.insert(tccStockOpe);
			}
			
			// 添加库存流水
			TccStockControlRunning tccStockControlRunning = null;
			{
				Long stockControlId = tccStockControl.getId();
				String guid2 = RandomUtil.getGUID();
				String guidStockControl = tccStockControl.getGuid();
				String bidRelative = tccStockOpe.getBid();
				String vGsBm = tccStockControl.getVgsbm();
				String productCode = tccStockControl.getProductCode();
				Integer productNumChange = productNum * -1;
				Integer productNumLeft = 0;
				String locationHw = tccStockControl.getVhw();
				String remark = "超过30天，系统自动出库";
				tccStockControlRunning = TccStockControlRunning.tccStockControlRunning(stockControlId, guid2, guidStockControl, bidRelative, vGsBm, productCode, productNumChange, productNumLeft, locationHw, remark, 1);
				tccStockControlRunningMapper.insert(tccStockControlRunning);
			}
		}
	}

	@Override
	public String getBidForAdd() {
		String yyMMdd = DateUtil.getYYYY_MM_DD(new Date()).replace("-", "").substring(2);
		
		String bid = diySqlMapper.getLatestBidOfStockOpe();
		if (bid == null) {
			return BID_PRE + "-" + yyMMdd + "-1001";
		} else {
			if (bid.startsWith(BID_PRE + "-" + yyMMdd)) {
				Integer bidLast = Integer.parseInt(bid.substring(bid.lastIndexOf("-") + 1)) + 1;
				return BID_PRE + "-" + yyMMdd + "-" + BidUtil.parseIntToFourLen(bidLast);
			} else {
				return BID_PRE + "-" + yyMMdd + "-1001";
			}
		}
	}

	@Override
	public void frozen(Long id, Integer num, Integer sourceType, String sourceBid, Long sourceId) throws Exception {
		// 验证库存ID
		if (id == null) {
			throw new RuntimeException("库存ID有误");
		}
		
		// 验证数量
		if (num == null || num <= 0) {
			throw new RuntimeException("数量必须为正");
		}

		TccStockControl tccStockControl = new TccStockControl().setId(id).queryFirst();
		if(tccStockControl.getProductNum() - num<0){
			throw new RuntimeException("库存数量不足以冻结");
		}
		
		storageMapper.frozenTccStockControl(id, num);
		
		// 添加冻结流水
		Long stockControlId = id;
		Integer numChange = num;
		Integer numLeft = storageMapper.getProductNumOfTccStockControl(stockControlId);
		TccStockFrozenRunning tccStockFrozenRunning = TccStockFrozenRunning.tccStockFrozenRunning(stockControlId, numChange, numLeft, sourceType, sourceBid, sourceId, 1);
		tccStockFrozenRunningMapper.insert(tccStockFrozenRunning);
	}

	@Override
	public void thaw(Long stockControlId, Integer num, Integer sourceType, String sourceBid, Long sourceId) throws Exception {
		// 验证库存ID
		if (stockControlId == null) {
			throw new RuntimeException("库存ID有误");
		}
		
		// 验证数量
		if (num == null || num <= 0) {
			throw new RuntimeException("数量必须为正");
		}
		
		storageMapper.thawTccStockControl(stockControlId, num);
		
		// 添加解冻流水
		Integer numChange = num * -1;
		Integer numLeft = storageMapper.getProductNumOfTccStockControl(stockControlId);
		TccStockFrozenRunning tccStockFrozenRunning = TccStockFrozenRunning.tccStockFrozenRunning(stockControlId, numChange, numLeft, sourceType, sourceBid, sourceId, 1);
		tccStockFrozenRunningMapper.insert(tccStockFrozenRunning);
	}

	/**
	 *
	 * 新增库存方法(包含流水)
	 * @param rkBid 入库单号
	 * @param chw 货位编码
	 * @param productName 商品名称
	 * @param productNum 可用数量
	 * @param productCode 商品编码
	 * @param productNumAll 商品总数量
	 * @param purchasePrice 采购单价
	 * @param purchaseTotalPriceAll  采购总价
	 * @param allotPrice 调拨单价
	 * @param totalAllotPrice 调拨总价
	 * @param sdays 库存天数
	 * @param vgsmc 公司名称
	 * @param vgsjc 公司简称
	 * @param vgsbm 公司编码
	 * @param drksj 入库时间
	 * @param isParent  是否母件
	 * @param sourceBid 来源单号
	 * @param sourceType 来源
	 * @param remark 流水备注
	 * @param companyVid 所属公司
	 * @param assembleBid 组装单号
	 * @param sourceId 来源id
	 * @return
	 * @throws Exception 
	 */
	@Override
	public R inWithRunning(String rkBid,String chw,String productName,Integer productNum,String productCode,Integer productNumAll,BigDecimal purchasePrice,
								BigDecimal purchaseTotalPriceAll,BigDecimal allotPrice,BigDecimal totalAllotPrice,String vgsbm,Date drksj,
								Integer isParent,String sourceBid,Integer sourceType ,String remark, String companyVid ,String assembleBid,Long sourceId
	) throws Exception {
		Map<String, Object> tccLocationMap = null;
		if (chw == null){
			throw new Exception();
		}
		
		//通过货位编码查询信息
		tccLocationMap = new TccLocation()
				.setChw(chw)
				.addLeftJoin("TCC_WarehouseArea B ON B.Ckq = A.Ckq")//库区
				.addLeftJoin("TCC_Warehouse C ON C.Cck = B.Cck")//仓库
				.setFields("C.Vck vck, B.Vkq vkq, A.Vhw vhw")
				.queryFirstMap();
		
		String vHw = tccLocationMap.get("vhw").toString();
		String vKq = tccLocationMap.get("vkq").toString();
		String vck = tccLocationMap.get("vck").toString();

		String guid = RandomUtil.getGUID();
		String rkGuid = RandomUtil.getGUID();
		String cid = null;

		Integer version = 0;
		String vgsmc = null;
		String vgsjc = hrMapper.getVgsjc(vgsbm);
		TccStockControl tccStockControlTo = TccStockControl.tccStockControl(guid, rkGuid, rkBid, cid, vHw,
				vKq, vck, productName, productCode, productNum,
				productNumAll, purchasePrice, purchaseTotalPriceAll, allotPrice, totalAllotPrice,
				null, null, null, null, null,
				vgsmc, vgsjc, vgsbm, drksj, isParent, version, chw, companyVid, 1);
		tccStockControlMapper.insert(tccStockControlTo);

		//新增库存流水
		TccStockControlRunning tccStockControlRunning = TccStockControlRunning.tccStockControlRunning(tccStockControlTo.getId(),RandomUtil.getGUID(),guid,rkBid,vgsbm,
				productCode,productNum,productNumAll,chw,remark,1);
		tccStockControlRunningMapper.insert(tccStockControlRunning);

		//新增流水对应的数据来源等字段信息
		TccStockSource tccStockSource = TccStockSource.tccStockSource(sourceType,sourceBid,sourceId,tccStockControlRunning.getId(),assembleBid,1,1);
		tccStockSourceMapper.insert(tccStockSource);
		return R.ok("新增成功",tccStockControlTo.getId());
	}


	/**
	 *  修改库存方法(包含流水)
	 * @param stockControlId 库存id
	 * @param remark 流水备注
	 * @param productNum  扣减的可用数量
	 * @param productNumAll 扣减的商品总数量
	 * @param sourceType 来源
	 * @param assembleBid 组装单号
	 * @param sourceId 来源id
	 * @return
	 */
	@Override
	public R outWithRunning(Long stockControlId, String remark,Integer numOut, String sourceBid,Integer sourceType,Long sourceId) {
		TccStockControl tccStockControl = new TccStockControl().setId(stockControlId).queryFirst();
		if(tccStockControl.getProductNum() - numOut<0 || tccStockControl.getProductNumAll() - numOut<0){
			throw new RuntimeException("库存数量不足以出库");
		}

		tccStockControl.setProductNum(tccStockControl.getProductNum() - numOut);
		tccStockControl.setProductNumAll(tccStockControl.getProductNumAll() - numOut);
		tccStockControlMapper.update(tccStockControl);

		//新增库存流水
		//Integer productNum = tccStockControl.getProductNum();
		TccStockControlRunning tccStockControlRunning = TccStockControlRunning.tccStockControlRunning(stockControlId, null, null, sourceBid,
				tccStockControl.getVgsbm(),
				tccStockControl.getProductCode(),numOut*-1,tccStockControl.getProductNum(),tccStockControl.getChw(),remark,1);
		tccStockControlRunningMapper.insert(tccStockControlRunning);

		//新增流水对应的数据来源等字段信息
		String assembleBid = storageMapper.getAssembleBidByStockControlId(stockControlId);
		TccStockSource tccStockSource = TccStockSource.tccStockSource(sourceType,sourceBid,sourceId,tccStockControlRunning.getId(),assembleBid,0,1);
		tccStockSourceMapper.insert(tccStockSource);
		return R.ok("修改成功",stockControlId);
	}
}
